package cn.broadsense.biz.service.impl;

import cn.broadsense.biz.bo.DataItemChannelBo;
import cn.broadsense.biz.bo.DataItemChannelQueryBo;
import cn.broadsense.biz.convert.DataItemConvert;
import cn.broadsense.biz.domain.Channel;
import cn.broadsense.biz.domain.DataItem;
import cn.broadsense.biz.dto.DataItemChannelDto;
import cn.broadsense.biz.mapper.*;
import cn.broadsense.biz.service.ChannelService;
import cn.broadsense.common.exception.ServiceException;
import cn.broadsense.common.utils.PageUtils;
import cn.broadsense.common.utils.SecurityUtils;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import cn.broadsense.biz.domain.DataItemChannel;
import cn.broadsense.biz.service.DataItemChannelService;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @author bs
 * @description 针对表【t_data_item_channel(数据接入点位)】的数据库操作Service实现
 * @createDate 2024-09-11 09:36:47
 */
@RequiredArgsConstructor
@Service
public class DataItemChannelServiceImpl extends ServiceImpl<DataItemChannelMapper, DataItemChannel>
        implements DataItemChannelService {

    private final ChannelService channelService;

    private final DataItemConvert dataItemConvert;

    private final DataItemChannelMapper dataItemChannelMapper;

    private final DataItemMapper dataItemMapper;



    @Override
    public List<Channel> listChannel(String keywords, Integer cameraType, Date start, Date end) {
        PageUtils.startPage();
        return dataItemChannelMapper.listChannel(keywords, cameraType, start, end);
    }

    @Override
    public List<DataItemChannel> findList(DataItemChannelQueryBo queryBo) {
        return super.lambdaQuery().eq(queryBo.getIsCollect() != null, DataItemChannel::getIsCollect, queryBo.getIsCollect())
                .eq(queryBo.getIsSync() != null, DataItemChannel::getIsSync, queryBo.getIsSync())
                .between(queryBo.getSyncTimeStart() != null && queryBo.getSyncTimeEnd() != null,
                        DataItemChannel::getSyncTime, queryBo.getSyncTimeStart(), queryBo.getSyncTimeEnd())
                .between(queryBo.getStartTime() != null && queryBo.getEndTime() != null, DataItemChannel::getCreateTime, queryBo.getStartTime(), queryBo.getEndTime())
                .and(StrUtil.isNotBlank(queryBo.getKeywords()), wrapper -> wrapper.like(DataItemChannel::getChannelName, queryBo.getKeywords()).or().like(DataItemChannel::getChannelCode, queryBo.getKeywords()))
                .eq(queryBo.getCameraType() != null, DataItemChannel::getCameraType, queryBo.getCameraType())
                .orderByDesc(DataItemChannel::getCreateTime)
                .list();
    }

    @Override
    public void saveChannelList(List<Long> channelIdList) {
        List<Channel> channelList = channelService.listByIds(channelIdList);
        if (CollUtil.isEmpty(channelList)) {
            throw new ServiceException("未找到对应的点位信息");
        }
        saveChannel(channelList);
    }


    @Override
    public void importChannelList(List<DataItemChannelBo> itemChannelList) {
        List<String> channelCodeList = itemChannelList.stream().map(DataItemChannelBo::getChannelCode).collect(Collectors.toList());
        List<Channel> list = channelService.list(Wrappers.<Channel>lambdaQuery().in(Channel::getChannelCode, channelCodeList));
        if (CollUtil.isEmpty(list)) {
            throw new ServiceException("未找到对应的点位信息");
        }
        this.saveChannel(list);
    }

    @Override
    public void batchRemove(List<Long> idList) {
        if (CollUtil.isEmpty(idList)) {
            return;
        }
        super.removeByIds(idList);
    }

    @Override
    public DataItemChannelDto getDetails(Long id) {
        DataItemChannel channel = super.getById(id);
        DataItemChannelDto dataItemChannel = dataItemConvert.toDataItemChannelDto(channel);
        if (dataItemChannel == null) {
            throw new ServiceException("未找到对应的接入点位信息");
        }
        return dataItemChannel;
    }

    @Override
    public void batchSyncData(List<Long> idList) {
        if (CollUtil.isEmpty(idList)) {
            throw new ServiceException("未找到对应的接入点位信息");
        }
        List<DataItemChannel> dataItemChannels = super.listByIds(idList);
        if (CollUtil.isEmpty(dataItemChannels)) {
            throw new ServiceException("未找到对应的接入点位信息");
        }

        List<Long> ids = new ArrayList<>();
        for (DataItemChannel dataItemChannel : dataItemChannels) {
            //查询审核的点位信息
            DataItem dataItem = dataItemMapper.selectOne(Wrappers.<DataItem>lambdaQuery().eq(DataItem::getChannelId, dataItemChannel.getChannelId()).eq(DataItem::getStatus, 3));
            if (dataItem == null) {
                throw new ServiceException(dataItemChannel.getChannelName() + "未找到已审核的事项数据，无法同步");
            }
            ids.add(dataItemChannel.getId());
        }
        //更新同步状态
        super.update(Wrappers.<DataItemChannel>lambdaUpdate().set(DataItemChannel::getIsSync, 1)
                .set(DataItemChannel::getSyncTime, new Date()).in(DataItemChannel::getId, ids));

    }

    /**
     * 保存接入点位信息
     *
     * @param channelList
     */
    private void saveChannel(List<Channel> channelList) {
        Date date = new Date();
        String username = SecurityUtils.getUsername();
        List<DataItemChannel> dataItemChannelList = CollUtil.newArrayList();
        for (Channel channel : channelList) {
            DataItemChannel dataItemChannel = new DataItemChannel();
            dataItemChannel.setChannelId(channel.getId());
            dataItemChannel.setChannelName(channel.getChannelName());
            dataItemChannel.setChannelCode(channel.getChannelCode());
            dataItemChannel.setCreateTime(date);
            dataItemChannel.setUpdateTime(date);
            dataItemChannel.setUpdateBy(username);
            dataItemChannel.setCreateBy(username);
            dataItemChannelList.add(dataItemChannel);
        }
        this.saveBatch(dataItemChannelList);
    }
}




